package com.jml.算法;


import org.junit.Test;

/**
 * @author:jml
 * @date: 2020/3/27 0027 8:51
 * @description：
  *
  * 给出两个 非空 的链表用来表示两个非负的整数。其中，它们各自的位数是按照 逆序 的方式存储的，并且它们的每个节点只能存储 一位 数字。
  * 如果，我们将这两个数相加起来，则会返回一个新的链表来表示它们的和。
  *
  * 您可以假设除了数字 0 之外，这两个数都不会以 0 开头。
  *
  * 示例：
  *
  * 输入：(2 -> 4 -> 3) + (5 -> 6 -> 4)
  * 输出：7 -> 0 -> 8
  * 原因：342 + 465 = 807
  *
  * 来源：力扣（LeetCode）
  * 链接：https://leetcode-cn.com/problems/add-two-numbers
  * 著作权归领扣网络所有。商业转载请联系官方授权，非商业转载请注明出处。
 */

public class 两数相加002 {
     /**
      * 链表结构
      */
     public class ListNode {
         int val;
         ListNode next;
         ListNode(int x) {
             val = x;
         }
     }

     @Test
    public void my(){
         ListNode listNode1 = new ListNode(2);
         ListNode listNode2 = new ListNode(4);
         ListNode listNode3 = new ListNode(3);
         listNode1.next = listNode2;
         listNode2.next = listNode3;
         ListNode listNode4 = new ListNode(5);
         ListNode listNode5 = new ListNode(6);
         ListNode listNode6 = new ListNode(4);
         listNode4.next = listNode5;
         listNode5.next = listNode6;
         System.out.println(listNode1);
         System.out.println(listNode4);
         my(listNode1,listNode4);
     }
    public ListNode my(ListNode l1, ListNode l2) {
        ListNode dummyHead = new ListNode(0);
        ListNode p = l1, q = l2, curr = dummyHead;
        int carry = 0;
        while(p != null || q != null){
            int x = (p!=null?p.val:0);
            int y = (q!=null?q.val:0);
            int sum = x+y+carry;
            int value = sum%10;
            carry = sum/10;
            curr.next=new ListNode(value);
            curr = curr.next;
            if (p != null) p = p.next;
            if (q != null) q = q.next;
        }
        if (carry > 0) {
            curr.next = new ListNode(carry);
        }
        return dummyHead.next;
    }


    //正常加法是从右往左相加，现在是逆序，所以就是从左往右加，可以直接从链表的节点相加。
    public ListNode other001(ListNode l1, ListNode l2) {
        ListNode dummyHead = new ListNode(0);
        ListNode p = l1, q = l2, curr = dummyHead;
        //carry就是需要进位的值，因为是逆序，第一个节点是十分位，第二个节点是百分位，(后一个节点的值为节点之和加上一个节点产生的进位)模 10
        int carry = 0;
        while (p != null || q != null) {
            int x = (p != null) ? p.val : 0;
            int y = (q != null) ? q.val : 0;
            int sum = carry + x + y;
            carry = sum / 10;
            curr.next = new ListNode(sum % 10);
            curr = curr.next;
            if (p != null) p = p.next;
            if (q != null) q = q.next;
        }
        //最后一位数之和如果是大于10，则需要进位
        //比如：[1,2,5][2,3,6]
        if (carry > 0) {
            curr.next = new ListNode(carry);
        }
        //过滤创建时候第一个为0的元素
        return dummyHead.next;
    }

}
